/* Copyright 2008 Bas van den Berg
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include "myassert.h"

#include "Area.h"
#include "Room.h"
#include "Error.h"
#include "MudPlayer.h"
#include "Utils.h"
#include "ElevatorController.h"
#include "StringBuilder.h"

using namespace Chronos;
using namespace std;


Area::Area(int id_, const std::string& name_)
	: id(id_)
	, name(name_)
	, controller(0)
{}


Area::~Area() {
    for (RoomsConstIter iter = rooms.begin(); iter != rooms.end(); ++iter) {
        delete iter->second;
    }
	delete controller;
}

const string& Area::getName() const { return name; }


void Area::addRoom(unsigned int id, Room& room) {
	RoomsConstIter iter = rooms.find(id);
	if (iter != rooms.end()) throw MudError(string("Area: already have roomID ") + Utils::itoa(id));
	rooms[id] = &room;
}


void Area::addPlayer(MudPlayer& player, int roomID, const string& arriveMsg) const {
    Room& room = getRoom(roomID);
    room.addPlayer(player, arriveMsg);
}


void Area::movePlayer(MudPlayer& player, int newRoomID, const string& leaveMsg, const string& arriveMsg) {
    Room* oldRoom = player.getRoom();
    ASSERT_NOT_NULL(oldRoom);
     
    Room& newRoom = getRoom(newRoomID);
    oldRoom->removePlayer(player, leaveMsg);
    newRoom.addPlayer(player, arriveMsg);
}


Room& Area::getRoom(int roomID) const {
    RoomsConstIter iter = rooms.find(roomID);
    if (iter == rooms.end()) {
        throw MudError(string("Area: cannot find dest room ") + Utils::itoa(roomID));
    }
    return *(iter->second);
}


void Area::printRooms(StringBuilder& buffer) const {
    for (RoomsConstIter iter = rooms.begin(); iter != rooms.end(); ++iter) {
        buffer << "  [" << iter->first << "] " << iter->second->getName() << '\n';
    }
}

